package com.qdsg.modulesihealsdk.camera;

import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.ImageFormat;
import android.graphics.Rect;
import android.graphics.YuvImage;
import android.hardware.Camera;
import android.media.FaceDetector;
import android.os.Handler;
import android.os.Looper;
import android.util.Log;
import android.view.SurfaceHolder;

import com.qdsg.modulesihealsdk.ui.FaceImage;

import java.io.ByteArrayOutputStream;
import java.io.IOException;

/**
 * @Description
 * @Author WuJianFeng
 * @Date 2022/11/15 14:06
 */
public class CameraUtils {
    private CameraCallback cameraCallback;
    private long detectStartTime;

    private CameraUtils(CameraCallback cameraCallback) {
        this.cameraCallback = cameraCallback;
    }

    public static volatile CameraUtils cameraUtils;

    public static CameraUtils getInstance(CameraCallback cameraCallback) {
        if (cameraUtils == null) {
            synchronized (CameraUtils.class) {
                if (cameraUtils == null) {
                    cameraUtils = new CameraUtils(cameraCallback);
                }
            }
        }
        return cameraUtils;
    }

    private Camera mCamera;
    private BitmapFactory.Options options = new BitmapFactory.Options();

    private FaceDetector faceDetector;
    private FaceDetector.Face faces[];


    /**
     * 开启摄像头 与视图
     */
    public void openCamera() {
        closeCamera();
        if (cameraCallback != null) {
            cameraCallback.openSuccess();
        }
    }

    /**
     * 关闭摄像头 与视图
     */
    public void closeCamera() {
        if (mCamera != null) {
            mCamera.stopPreview();
            mCamera.setPreviewCallback(null);
            mCamera.stopPreview();
            mCamera.release();
            mCamera = null;
        }
    }

    /**
     * 定义“拍照”方法
     */
    public void capture(Camera.PictureCallback pictureCallback) {
        Handler captureHandler = new Handler(Looper.getMainLooper());
        captureHandler.post(() -> {
            Camera.Parameters parameters = mCamera.getParameters();
            parameters.setPictureFormat(ImageFormat.JPEG);//设置照片格式
            parameters.setPreviewSize(800, 400);
            parameters.setFocusMode(Camera.Parameters.FOCUS_MODE_AUTO);
            //摄像头聚焦
            mCamera.autoFocus(new Camera.AutoFocusCallback() {
                @Override
                public void onAutoFocus(boolean success, Camera camera) {
                    if (success) {
                        mCamera.takePicture(null, null, pictureCallback);
                    }
                }
            });
        });
    }

    public SurfaceHolder.Callback mSurfaceCallback = new SurfaceHolder.Callback() {
        /**
         *  在 Surface 首次创建时被立即调用：活得叫焦点时。一般在这里开启画图的线程
         * @param surfaceHolder 持有当前 Surface 的 SurfaceHolder 对象
         */
        @Override
        public void surfaceCreated(SurfaceHolder surfaceHolder) {
            if (mCamera != null) {
                return;
            }
            try {
                surfaceHolder.addCallback(this);
                surfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);

                // Camera,open() 默认返回的后置摄像头信息
                if (mCamera == null) {
                    mCamera = Camera.open(0);

                    //mCamera = Camera.open(0);//打开硬件摄像头，这里导包得时候一定要注意是android.hardware.Camera
                    // mCamera.lock();
                    Camera.Parameters parameters = mCamera.getParameters();//得到摄像头的参数
                    parameters.setPictureFormat(ImageFormat.JPEG);
                    parameters.set("jpeg-quelity", 85);
                    parameters.setPictureSize(640, 480);

                    //设置角度，此处 CameraId 我默认 为 0 （后置）
                    // CameraId 也可以 通过 参考 Camera.open() 源码 方法获取
                    //setCameraDisplayOrientation(getActivity(), 0, mCamera);
                    mCamera.setPreviewDisplay(surfaceHolder);//通过SurfaceView显示取景画面
                    //mCamera.unlock();
                    try {
                        mCamera.startPreview();//开始预览
                    } catch (RuntimeException e) {
                        e.printStackTrace();
                    }

                    if (cameraCallback != null) {
                        cameraCallback.previewSuccess();
                    }
                }
            } catch (IOException e) {
            }
        }

        /**
         *  在 Surface 格式 和 大小发生变化时会立即调用，可以在这个方法中更新 Surface
         * @param surfaceHolder   持有当前 Surface 的 SurfaceHolder 对象
         * @param format          surface 的新格式
         * @param width           surface 的新宽度
         * @param height          surface 的新高度
         */
        @Override
        public void surfaceChanged(SurfaceHolder surfaceHolder, int format, int width, int height) {

        }

        /**
         *  在 Surface 被销毁时立即调用：失去焦点时。一般在这里将画图的线程停止销毁
         * @param surfaceHolder 持有当前 Surface 的 SurfaceHolder 对象
         */
        @Override
        public void surfaceDestroyed(SurfaceHolder surfaceHolder) {
        }


    };


    /**
     * 获取鬼脸包
     */
    public void getPreViewImage(PreViewImageCallback preViewImageCallback) {
        if (mCamera == null) {
            return;
        }
        // 画鬼脸
        if (preViewImageCallback != null) {
            preViewImageCallback.setCanCapture();
        }
        detectStartTime = System.currentTimeMillis();
        mCamera.setPreviewCallback(new Camera.PreviewCallback() {
            @Override
            public void onPreviewFrame(byte[] data, Camera camera) {
                long timestamp = System.currentTimeMillis();
                if (timestamp - detectStartTime < 3000) {
                    return;
                }
                detectStartTime = timestamp;
                Camera.Size size = camera.getParameters().getPreviewSize();
                try {
                    YuvImage image = new YuvImage(data, ImageFormat.NV21, size.width, size.height, null);
                    if (image != null) {
                        ByteArrayOutputStream stream = new ByteArrayOutputStream();
                        image.compressToJpeg(new Rect(0, 0, size.width, size.height), 90, stream);
                        options.inPreferredConfig = Bitmap.Config.RGB_565;
                        Bitmap bmp = BitmapFactory.decodeByteArray(stream.toByteArray(), 0, stream.size(), options);
                        //bmp = rotateBitmap(bmp, -90f);//图像向左旋转了90度
                        /*  //bmp = Resize.resize(mRs, bmp, 90, 160);//90：160 暂时固定写法
                        bmp = bmp.copy(Bitmap.Config.RGB_565, true);//必须设置*/
                        faceDetector = new FaceDetector(640, 480, 1);
                        faces = new FaceDetector.Face[1];
                        Log.e("---", "findFaces: " + "size.width" + size.width + "size.height" + size.height);
                        int faceNum = faceDetector.findFaces(bmp, faces);
                        Log.e("---", "findFaces: " + faceNum);
                        if (faceNum > 0) {
                            FaceImage faceImage = new FaceImage(faceNum, faces, stream.toByteArray(), timestamp);

                            if (preViewImageCallback != null) {
                                preViewImageCallback.onFacesDetected(faceNum, faces, stream.toByteArray(), timestamp, bmp, faceImage);
                            }

                        } else {
                            if (preViewImageCallback != null) {
                                preViewImageCallback.onFacesClear();
                            }
                        }
                        stream.close();
                        bmp.recycle();
                    }
                } catch (Exception ex) {
                    ex.printStackTrace();
                }
            }
        });
    }
}
